package com.gx.smart.building.ui.common.activity;

import android.app.Activity;
import android.content.ContentValues;
import android.content.Intent;
import android.database.Cursor;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Color;
import android.net.Uri;
import android.os.AsyncTask;
import android.os.Build;
import android.os.Bundle;
import android.os.Environment;
import android.os.ParcelFileDescriptor;
import android.provider.MediaStore;
import android.text.TextUtils;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.view.ViewStub;
import android.widget.ImageView;
import android.widget.RelativeLayout;
import android.widget.TextView;

import androidx.annotation.LayoutRes;
import androidx.appcompat.app.AppCompatActivity;
import androidx.core.content.FileProvider;
import androidx.lifecycle.ViewModelProvider;

import com.blankj.utilcode.util.BarUtils;
import com.blankj.utilcode.util.ImageUtils;
import com.blankj.utilcode.util.ToastUtils;
import com.gx.smart.base.BaseAdapter;
import com.gx.smart.base.BaseViewModel;
import com.gx.smart.base.databinding.ActivityRoot2Binding;
import com.gx.smart.base.loading.LoadingView;
import com.gx.smart.building.ui.common.adapter.AttachmentAdapter;
import com.gx.smart.building.ui.common.model.AttachmentInfo;
import com.gx.smart.building.ui.common.model.UploadImage;
import com.mylhyl.circledialog.CircleDialog;
import com.orhanobut.logger.Logger;
import com.yanzhenjie.permission.AndPermission;
import com.yanzhenjie.permission.runtime.Permission;

import org.greenrobot.eventbus.EventBus;

import java.io.File;
import java.io.FileDescriptor;
import java.util.ArrayList;
import java.util.List;

/**
 * 基础activity
 * 带EditText的界面
 * 统一处理带EditText界面的title问题
 */

public abstract class BaseMVVMActivityUploadFileV3<VM extends BaseViewModel> extends AppCompatActivity {

    public static final int IMAGE_MAX_COUNT = 3;
    //请求相机
    private static final int REQUEST_CAPTURE = 100;
    //请求相册
    private static final int REQUEST_PICK = 101;
    //请求 setting 权限设置界面
    private static final int REQUEST_CODE_SETTING = 0x01;
    protected VM viewModel;
    protected ActivityRoot2Binding binding;
    protected LoadingView mLoadingInitView;
    protected View mNoDataView;
    protected TextView mTxtTitle;
    protected TextView mLeft;
    protected TextView mRight;
    protected ImageView mRightImage;
    protected RelativeLayout mViewStubContent;
    /***********************第一个上传*********************************/
    protected List<UploadImage> picList1 = new ArrayList<>(); //上传后的图片地址
    protected List<AttachmentInfo> attachmentList1 = new ArrayList<>(); //图片附件显示
    protected AttachmentAdapter attachmentAdapter1;
    private ViewStub mViewStubToolbar;
    private ViewStub mViewStubInitLoading;
    private ViewStub mViewStubNoData;
    //调用照相机返回图片文件
    private File tempFile;
    private final String[] items = {"选择本地照片", "拍照"};
    private Uri cameraUri = null;

    public void initAdapter1() {
        attachmentAdapter1 = new AttachmentAdapter(this);
        attachmentAdapter1.setItemClickListener((BaseAdapter.OnItemClickListener<AttachmentInfo>) (attachmentInfo, position) -> {
            if (attachmentInfo.getType() == 1) {
                deleteImage1(attachmentInfo, position);
            }

            if (attachmentInfo.getType() == 2) {
                uploadImage1();
            }

            if (attachmentAdapter1.getItemCount() < IMAGE_MAX_COUNT) {
                AttachmentInfo item = new AttachmentInfo();
                item.setType(2);
                if (!attachmentList1.contains(item)) {
                    attachmentList1.add(item);
                }
            }

            if (attachmentAdapter1.getItemCount() >= IMAGE_MAX_COUNT && attachmentInfo.getType() == 2) {
                attachmentList1.remove(IMAGE_MAX_COUNT - 1);
            }
            attachmentAdapter1.refresh(attachmentList1);
        });
        AttachmentInfo attachmentInfo = new AttachmentInfo();
        attachmentInfo.setType(2);//type 附件类型 1：图片 2：显示add image图片
        attachmentList1.add(attachmentInfo);
        attachmentAdapter1.addAll(attachmentList1);
    }


    /**
     * 删除上传的图片
     */
    private void deleteImage1(AttachmentInfo attachmentInfo, int position) {
        new CircleDialog.Builder()
                .setTitle("删除图片")
                .setWidth(0.8f)
                .setText("你确定要删除上传图片?")
                .setNegative("取消", null)
                .setPositive("确定", new View.OnClickListener() {
                    @Override
                    public void onClick(View v) {
                        attachmentList1.remove(position);

                        attachmentAdapter1.refresh(attachmentList1);

                        if (attachmentAdapter1.getItemCount() <= IMAGE_MAX_COUNT) {
                            AttachmentInfo item = new AttachmentInfo();
                            item.setType(2);
                            if (!attachmentList1.contains(item)) {
                                attachmentList1.add(item);
                            }
                        }
                        attachmentAdapter1.refresh(attachmentList1);
                    }
                })
                .show(getSupportFragmentManager());
    }


    /**
     * 上传图片
     */
    protected void uploadImage1() {
        new CircleDialog.Builder()
                .setItems(items, (parent, view, position, id) -> {
                    handleEvent1(position);
                    return true;
                })
                .setNegative("取消", null)
                .show(getSupportFragmentManager());
    }


    /**
     * 跳转到相册
     */
    private void gotoPhoto1() {
        Logger.d("*****************打开图库********************");
        //跳转到调用系统图库
        Intent intent = new Intent(Intent.ACTION_PICK, MediaStore.Images.Media.EXTERNAL_CONTENT_URI);
        startActivityForResult(Intent.createChooser(intent, "请选择图片"), REQUEST_PICK);
    }

    /**
     * 跳转到照相机
     */
    private void gotoCamera1() {
        Logger.d("*****************打开相机********************");
        //创建拍照存储的图片文件

        //跳转到调用系统相机
        Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) {
            Uri uri = createImageUri();
            cameraUri = uri;
            intent.setFlags(Intent.FLAG_GRANT_WRITE_URI_PERMISSION);
            intent.putExtra(MediaStore.EXTRA_OUTPUT, uri);
        } else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N && Build.VERSION.SDK_INT < Build.VERSION_CODES.Q) {
            //设置7.0中共享文件，分享路径定义在xml/file_paths.xml
            tempFile = createFile();
            intent.setFlags(Intent.FLAG_GRANT_WRITE_URI_PERMISSION);
            Uri contentUri = FileProvider.getUriForFile(this,
                    getApplication().getPackageName() + ".fileProvider", tempFile);
            intent.putExtra(MediaStore.EXTRA_OUTPUT, contentUri);
        } else {
            tempFile = createFile();
            intent.putExtra(MediaStore.EXTRA_OUTPUT, Uri.fromFile(tempFile));
        }
        startActivityForResult(intent, REQUEST_CAPTURE);
    }


    private File createFile() {
        File storageDir = getExternalFilesDir(Environment.DIRECTORY_PICTURES);
        if (!storageDir.exists()) {
            storageDir.mkdir();
        }
        return new File(storageDir, System.currentTimeMillis() + ".jpg");
    }


    public void handleEvent1(int position) {
        switch (position) {
            case 0: // 选择本地照片,跳转到相册
                //权限判断
                AndPermission.with(this)
                        .runtime()
                        .permission(Permission.READ_EXTERNAL_STORAGE, Permission.WRITE_EXTERNAL_STORAGE)
                        .onGranted(permissions -> {
                            //跳转到相册
                            gotoPhoto1();
                        })
                        .onDenied(permissions -> {
                            ToastUtils.showLong("没有获取访问相册的权限");
                            if (AndPermission.hasAlwaysDeniedPermission(this, permissions)) {
                                new CircleDialog.Builder()
                                        .setTitle("系统权限设置")
                                        .setText("您确定要获取访问相册的权限吗？")
                                        .setPositive("确定", new View.OnClickListener() {
                                            @Override
                                            public void onClick(View v) {
                                                setPermission();
                                            }
                                        })
                                        .setNegative("取消", null)
                                        .show(getSupportFragmentManager());
                            }
                        }).start();

                break;
            case 1: // 拍照,跳转到调用系统相机
                //权限判断
                AndPermission.with(this)
                        .runtime()
                        .permission(Permission.CAMERA)
                        .onGranted(permissions -> {
                            //跳转到调用系统相机
                            gotoCamera1();
                        })
                        .onDenied(permissions -> {
                            ToastUtils.showLong("没有获取访问相机的权限");
                            if (AndPermission.hasAlwaysDeniedPermission(this, permissions)) {
                                new CircleDialog.Builder()
                                        .setTitle("系统权限设置")
                                        .setText("您确定要获取访问相机的权限吗？")
                                        .setPositive("确定", new View.OnClickListener() {
                                            @Override
                                            public void onClick(View v) {
                                                setPermission();
                                            }
                                        })
                                        .setNegative("取消", null)
                                        .show(getSupportFragmentManager());
                            }

                        }).start();
                break;
        }
    }


    /**
     * Set permissions.
     */
    protected void setPermission() {
        AndPermission.with(this).runtime().setting().start(REQUEST_CODE_SETTING);
    }


    @Override
    public void onActivityResult(int requestCode, int resultCode, Intent intent) {
        super.onActivityResult(requestCode, resultCode, intent);
        switch (requestCode) {
            case REQUEST_CAPTURE: //调用系统相机返回
                if (resultCode == Activity.RESULT_OK) {
                    if (cameraUri != null) {
                        String fileName = getFileNameByUri(cameraUri);
                        displayImage1(fileName, cameraUri);
                        new UploadImageAsyncTask1().execute(cameraUri);
                    } else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N && Build.VERSION.SDK_INT < Build.VERSION_CODES.Q) {
                        Uri contentUri = FileProvider.getUriForFile(this,
                                getApplication().getPackageName() + ".fileProvider", tempFile);
                        String fileName = getFileNameByUri(contentUri);
                        displayImage1(fileName, contentUri);
                        new UploadImageAsyncTask1().execute(contentUri);
                    } else {
                        Uri uri = Uri.fromFile(tempFile);
                        String fileName = getFileNameByUri(uri);
                        displayImage1(fileName, uri);
                        new UploadImageAsyncTask1().execute(uri);
                    }
                }
                break;
            case REQUEST_PICK:  //调用系统相册返回
                if (resultCode == Activity.RESULT_OK) {
                    Uri uri = intent.getData();
                    String fileName = getFileNameByUri(uri);
                    displayImage1(fileName, uri);
                    new UploadImageAsyncTask1().execute(uri);
                }
                break;
            case REQUEST_CODE_SETTING:
                if (resultCode == Activity.RESULT_OK) {
                }
                break;

        }
    }


    /**
     * 在ImageView上显示图片
     *
     * @param uri
     */

    public void displayImage1(String fileName, Uri uri) {
        AttachmentInfo item = new AttachmentInfo();
        item.setFileName(fileName);
        item.setType(1);
        item.setUri(uri);
        attachmentList1.add(attachmentList1.size() - 1, item);
        attachmentAdapter1.refresh(attachmentList1);
    }


    /**
     * 创建图片地址uri,用于保存拍照后的照片 Android 10以后使用这种方法
     */
    private Uri createImageUri() {
        ContentValues values = new ContentValues();
        values.put(MediaStore.MediaColumns.DISPLAY_NAME, System.currentTimeMillis() + ".jpg");
        values.put(MediaStore.MediaColumns.MIME_TYPE, "image/jpeg");
        values.put(MediaStore.MediaColumns.RELATIVE_PATH, Environment.DIRECTORY_PICTURES);
        String status = Environment.getExternalStorageState();
        // 判断是否有SD卡,优先使用SD卡存储,当没有SD卡时使用手机存储
        Uri uri;
        if (status.equals(Environment.MEDIA_MOUNTED)) {
            uri = getContentResolver().insert(
                    MediaStore.Images.Media.EXTERNAL_CONTENT_URI,
                    values
            );

        } else {
            uri = getContentResolver().insert(
                    MediaStore.Images.Media.INTERNAL_CONTENT_URI,
                    values
            );
        }
        return uri;
    }


    // 通过uri加载图片
    private Bitmap getBitmapFromUri(Uri uri) {
        try {
            ParcelFileDescriptor parcelFileDescriptor =
                    getContentResolver().openFileDescriptor(uri, "r");
            FileDescriptor fileDescriptor = parcelFileDescriptor.getFileDescriptor();
            Bitmap image = BitmapFactory.decodeFileDescriptor(fileDescriptor);
            parcelFileDescriptor.close();
            return image;
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }

    protected void uploadImage1(Uri uri) {
        String fileName = getFileNameByUri(uri);
        Logger.d("uploadImage fileName=" + fileName);
        Bitmap bitmap = getBitmapFromUri(uri);
        Logger.d("uploadImage bitmap : " + bitmap != null);
        Bitmap newBitmap = ImageUtils.compressBySampleSize(bitmap, 500, 500);
        Logger.d("newBitmap size:" + newBitmap.getByteCount());
        byte[] file = ImageUtils.bitmap2Bytes(newBitmap, Bitmap.CompressFormat.JPEG, 100);
        uploadTask1(fileName, file);
        Logger.d("uploadImage fileName=" + fileName);
    }


    private String getFileNameByUri(Uri uri) {
        String fileName = String.valueOf(System.currentTimeMillis());
        Cursor cursor = getContentResolver().query(uri, null, null, null, null);
        if (cursor != null && cursor.getCount() > 0) {
            cursor.moveToFirst();
            fileName = cursor.getString(cursor.getColumnIndexOrThrow(MediaStore.MediaColumns.DISPLAY_NAME));
            cursor.close();
        }
        return fileName;
    }

    /**
     * 该方法在子线程中不能刷新UI
     *
     * @param fileName
     */
    public abstract void uploadTask1(String fileName, byte[] file);

    /**
     * 上传附件同步信息
     */
    protected boolean uploadImageAttachment1() {
        //不包含Add image 文件数量
        int realSize = attachmentList1.size();
        AttachmentInfo addItem = new AttachmentInfo();
        addItem.setType(2);//type 附件类型 1：图片 2：显示add image图片
        if (attachmentList1.contains(addItem)) {
            realSize = realSize - 1;
        }

        for (AttachmentInfo item : attachmentList1) {
            if (item.isFail()) {
                ToastUtils.showLong("请删除上传失败图片，重新上传");
                return false;
            }
        }

        if (picList1.size() < realSize) {
            ToastUtils.showLong("图片还没上传完成，请耐心等待");
            return false;
        }

        return true;

    }

    /**
     * 显示上传失败
     *
     * @param fileName
     */
    protected void displayFailImage1(String fileName) {
        for (AttachmentInfo item : attachmentList1) {
            if (item.getType() != 2 && item.getFileName().equals(fileName)) {
                item.setFail(true);
                break;
            }
        }
        attachmentAdapter1.notifyDataSetChanged();
    }

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        initStatusBar();
        binding = ActivityRoot2Binding.inflate(getLayoutInflater());
        setContentView(binding.getRoot());
        initViewModel();
        initView();
        initContent();
        initData();
        initObserver();
    }

    private void initViewModel() {
        viewModel = new ViewModelProvider(this, ViewModelProvider.AndroidViewModelFactory.getInstance(getApplication())).get(onBindViewModel());
    }

    protected void initData() {

    }

    protected void initObserver() {

    }

    protected abstract Class<VM> onBindViewModel();

    /**
     * 绑定布局
     *
     * @return
     */
    @LayoutRes
    protected abstract int onBindLayout();

    @Override
    protected void onDestroy() {
        super.onDestroy();
    }

    protected void registerEventBus() {
        if (!EventBus.getDefault().isRegistered(this)) {
            EventBus.getDefault().register(this);
        }
    }

    protected void unregisterEventBus() {
        if (EventBus.getDefault().isRegistered(this)) {
            EventBus.getDefault().removeAllStickyEvents();
            EventBus.getDefault().unregister(this);
        }
    }

    protected void initStatusBar() {
        BarUtils.setStatusBarColor(this, Color.TRANSPARENT);
        BarUtils.setStatusBarLightMode(this, true);
    }

    protected void initView() {

    }

    protected void initContent() {
        initCommonView();
    }

    public void initCommonView() {
        ViewGroup.LayoutParams params = binding.statusBar.getLayoutParams();
        params.height = BarUtils.getStatusBarHeight();
        binding.statusBar.setLayoutParams(params);

        mViewStubToolbar = findViewById(com.gx.smart.base.R.id.view_stub_toolbar);
        mViewStubContent = findViewById(com.gx.smart.base.R.id.view_stub_content);
        mViewStubInitLoading = findViewById(com.gx.smart.base.R.id.view_stub_init_loading);
        mViewStubNoData = findViewById(com.gx.smart.base.R.id.view_stub_nodata);

        if (enableToolbar()) {
            mViewStubToolbar.setLayoutResource(onBindToolbarLayout());
            View viewTooBar = mViewStubToolbar.inflate();
            initTooBar(viewTooBar);
        }
        initContentView(mViewStubContent);
    }

    public void initContentView(ViewGroup root) {
        LayoutInflater.from(this).inflate(onBindLayout(), root, true);
    }

    public int onBindToolbarLayout() {
        return com.gx.smart.base.R.layout.layout_common_title;
    }

    public boolean enableToolbar() {
        return true;
    }

    protected void initTooBar(View view) {
        mLeft = view.findViewById(com.gx.smart.base.R.id.left);
        mTxtTitle = view.findViewById(com.gx.smart.base.R.id.center_title);
        mRight = view.findViewById(com.gx.smart.base.R.id.right);
        mRightImage = view.findViewById(com.gx.smart.base.R.id.rightImageView);
        if (getLeft()) {
            mLeft.setVisibility(View.VISIBLE);
            mLeft.setOnClickListener(v -> onBackPressed());
        }

        if (!TextUtils.isEmpty(getToolbarTitle())) {
            mTxtTitle.setVisibility(View.VISIBLE);
            mTxtTitle.setText(getToolbarTitle());
        }

        if (!TextUtils.isEmpty(getRight())) {
            mRight.setVisibility(View.VISIBLE);
            mRight.setText(getRight());
        }

        if (getRightImage() != -1) {
            mRightImage.setVisibility(View.VISIBLE);
            mRightImage.setImageResource(getRightImage());
        }
    }

    public abstract String getToolbarTitle();

    public boolean getLeft() {
        return true;
    }

    public String getRight() {
        return "";
    }

    public int getRightImage() {
        return -1;
    }

    public void showInitLoadView(boolean show) {
        if (mLoadingInitView == null) {
            View view = mViewStubInitLoading.inflate();
            mLoadingInitView = view.findViewById(com.gx.smart.base.R.id.loadingView);
        }
        mLoadingInitView.setVisibility(show ? View.VISIBLE : View.GONE);
    }

    public void showNoDataView(boolean show) {
        if (mNoDataView == null) {
            View view = mViewStubNoData.inflate();
            mNoDataView = view.findViewById(com.gx.smart.base.R.id.view_no_data);
        }
        mNoDataView.setVisibility(show ? View.VISIBLE : View.GONE);
    }

    protected class UploadImageAsyncTask1 extends AsyncTask<Uri, Void, Void> {


        @Override
        protected Void doInBackground(Uri... uris) {
            uploadImage1(uris[0]);
            return null;
        }
    }


}